package com.heima.article.service.impl;

import com.alibaba.fastjson.JSON;
import com.heima.apis.wemedia.IWemediaClient;
import com.heima.article.mapper.ApArticleMapper;
import com.heima.article.service.HotArticleService;
import com.heima.common.constants.ArticleConstants;
import com.heima.common.redis.CacheService;
import com.heima.model.article.pojos.ApArticle;
import com.heima.model.article.vos.HotArticleVo;
import com.heima.model.common.dtos.ResponseResult;
import com.heima.model.wemedia.pojos.WmChannel;
import lombok.extern.slf4j.Slf4j;
import org.joda.time.DateTime;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.ArrayList;
import java.util.Comparator;
import java.util.Date;
import java.util.List;
import java.util.stream.Collectors;

@Service
@Slf4j
@Transactional
public class HotArticleServiceImpl implements HotArticleService {


    @Autowired
    private ApArticleMapper apArticleMapper;


    @Autowired
    private CacheService cacheService;

    @Autowired
    private IWemediaClient wemediaClient;

    //    查询热点文章
    @Override
    public void computeHotArticle() {

//        查询前五天的文章数据
        Date date = DateTime.now().minusDays(5).toDate();
        List<ApArticle> articles = apArticleMapper.findArticleListByLast5days(date);

//        计算得分的所有文章
        List<HotArticleVo> hotArticleVoList = queryScorearticles(articles);

//        查询每个频道的前30数据
        querywmChannelsAparticle(hotArticleVoList);


    }

    //        查询每个频道的前30数据
    private void querywmChannelsAparticle(List<HotArticleVo> hotArticleVoList) {

        //        获取频道数据
        ResponseResult responseResult = wemediaClient.getChannels();

        if (responseResult != null) {
            String jsonString = JSON.toJSONString(responseResult.getData());
//            转化为频道数据
            List<WmChannel> wmChannels = JSON.parseArray(jsonString, WmChannel.class);

//            匹配频道对应的文章
            for (WmChannel wmChannel : wmChannels) {
                List<HotArticleVo> articleVos = hotArticleVoList.stream().filter(item -> item.getChannelId()
                        .equals(wmChannel.getId())).collect(Collectors.toList());
                if (articleVos != null && articleVos.size() > 0){
//                    进行排数
                            articleVos = articleVos.stream().sorted(Comparator.comparing(HotArticleVo::getScore)
                            .reversed()).collect(Collectors.toList());
//                取出30条数据
                    if (articleVos.size() > 0) {
//                    取出前30条数据
                        articleVos = articleVos.subList(0, 30);
                    }
//                设置到redis数据中
                    cacheService.set(ArticleConstants.HOT_ARTICLE_FIRST_PAGE + wmChannel.getId(), JSON.toJSONString(articleVos));
                }
//
            }

        }
//            查询推荐数据
        hotArticleVoList = hotArticleVoList.stream().sorted(Comparator.comparing(HotArticleVo::getScore)
                .reversed()).collect(Collectors.toList());
//                取出30条数据
        if (hotArticleVoList.size() > 0) {
//                    取出前30条数据
            hotArticleVoList = hotArticleVoList.subList(0, 30);
        }
//                设置到redis数据中
        cacheService.set(ArticleConstants.DEFAULT_TAG, JSON.toJSONString(hotArticleVoList));
    }

    //        计算文章得分
    private List<HotArticleVo> queryScorearticles(List<ApArticle> articles) {

        List<HotArticleVo> hotArticleVos = new ArrayList<>();

        for (ApArticle apArticle : articles) {

            HotArticleVo hotArticleVo = new HotArticleVo();

            BeanUtils.copyProperties(apArticle, hotArticleVo);

//            计算得分
            Integer count = computeScore(apArticle);

            hotArticleVo.setScore(count);

            hotArticleVos.add(hotArticleVo);
        }
        return hotArticleVos;
    }

    private Integer computeScore(ApArticle apArticle) {
        Integer scere = 0;
        if (apArticle.getLikes() != null) {
            scere += apArticle.getLikes() * ArticleConstants.HOT_ARTICLE_LIKE_WEIGHT;
        }
        if (apArticle.getViews() != null) {
            scere += apArticle.getViews();
        }
        if (apArticle.getComment() != null) {
            scere += apArticle.getComment() * ArticleConstants.HOT_ARTICLE_COMMENT_WEIGHT;
        }
        if (apArticle.getCollection() != null) {
            scere += apArticle.getCollection() * ArticleConstants.HOT_ARTICLE_COLLECTION_WEIGHT;
        }

        return scere;

    }
}
